package com.geek.zookeeper.curator.controller;

import com.geek.controller.BaseController;
import com.geek.exception.OrderException;
import com.geek.resp.Response;
import com.geek.zookeeper.curator.entity.ZooOrder;
import com.geek.zookeeper.curator.entity.ZooProduct;
import com.geek.zookeeper.curator.services.ZooOrderRepository;
import com.geek.zookeeper.curator.services.ZooProductRepository;
import lombok.extern.slf4j.Slf4j;
import org.apache.curator.framework.CuratorFramework;
import org.apache.curator.framework.recipes.locks.InterProcessMutex;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.interceptor.TransactionAspectSupport;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.transaction.Transactional;
import java.util.Date;
import java.util.Optional;

@Slf4j
@RestController
@RequestMapping(path = "/api/zoo/order")
public class OrderController extends BaseController<ZooOrder> {

	@Autowired
	private ZooOrderRepository orderRepository;

	@Autowired
	private ZooProductRepository productRepository;

	@Autowired
	private CuratorFramework curatorFramework;

	/**
	 * 模拟下单逻辑
	 */
	@Transactional
	@PostMapping(path = "/order")
	public Response order(long id) {
		Response response = new Response();

		InterProcessMutex interProcessMutex = new InterProcessMutex(curatorFramework, "/zoo_lock_"+id);

		try{
			interProcessMutex.acquire();

			//获取产品
			Optional<ZooProduct> oProduct = productRepository.findById(id);
			if(!oProduct.isPresent()){
				throw new OrderException("产品不存在！");
			}
			ZooProduct product = oProduct.get();
			log.info("获取产品："+ product);

			//模拟其他操作造成的延迟
			Thread.sleep(500);

			int stock = product.getStock();
			if(stock <= 0){
				throw new OrderException("库存不足！");
			}

			//保存订单
			ZooOrder order = new ZooOrder();
			order.setProduct(product);
			order.setCreateDate(new Date());
			order.setUpdateDate(new Date());
			orderRepository.save(order);

			//更新库存
			productRepository.updateStock(id);

			response.success("下单成功");
		}catch (Exception e){
//			e.printStackTrace();
			log.error(e.getMessage());
			response.fail("下单失败，"+e.getMessage());
			//事务回滚
			TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
		}finally {
			try {
				interProcessMutex.release();
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
		return response;
	}

}
